#include <string>       // 包含字符串处理库
#include <map>          // 包含映射容器库
#include <memory>       // 包含智能指针库
#include <functional>   // 包含函数对象库
#include <iostream>     // 包含输入输出流库

using namespace std;    // 使用标准命名空间

// IoC 容器类模板定义
template <class T>
class IocContainer {
public:
    IocContainer() {}   // 构造函数
    ~IocContainer() {}  // 析构函数

    // 注册类型的方法模板
    template<class Drived>
    void RegisterType(string strKey) {
        // 创建一个函数对象，用于创建 Drived 类型对象
        std::function<T* ()> function = [] { return new Drived(); };
        // 调用内部的注册方法进行注册
        RegisterType(strKey, function);
    }

    // 解析类型的方法，通过键获取对象实例
    T* Resolve(string strKey) {
        // 检查键是否存在于创建映射中
        if (m_createMap.find(strKey) == m_createMap.end())
            return nullptr;  // 如果不存在，返回空指针
        // 获取创建对象的函数
        std::function<T* ()> function = m_createMap[strKey];
        // 调用函数创建对象并返回
        return function();
    }

    // 解析类型的方法，通过键获取共享指针对象实例
    std::shared_ptr<T> ResolveShared(string strKey) {
        // 调用 Resolve 方法获取原始指针
        T* ptr = Resolve(strKey);
        // 将原始指针包装为共享指针并返回
        return std::shared_ptr<T>(ptr);
    }

private:
    // 内部注册类型的方法
    void RegisterType(string strKey, std::function<T* ()> creator) {
        // 检查键是否已经存在于映射中
        if (m_createMap.find(strKey) != m_createMap.end()) {
            throw std::invalid_argument("该键已存在");  // 如果存在，抛出异常
        }
        // 将键和值（创建函数）添加到映射中
        m_createMap.emplace(strKey, creator);
    }

    // 存储创建函数的映射
    map<string, std::function<T* ()>> m_createMap;
};

// ICar 接口类
struct ICar {
    virtual ~ICar() {}              // 虚析构函数
    virtual void test() const = 0;  // 纯虚函数
};

// Bus 类，实现 ICar 接口
struct Bus : ICar {
    Bus() {}                        // 构造函数
    void test() const {             // 实现 test 方法
        std::cout << "Bus::test()" << endl;
    }
};

// Track 类，实现 ICar 接口
struct Track : ICar {
    Track() {}                      // 构造函数
    void test() const {             // 实现 test 方法
        std::cout << "Track::test()" << endl;
    }
};

int main() {
    // 创建 IoC 容器实例
    IocContainer<ICar> carIOC;

    // 注册 Bus 和 Track 类型
    carIOC.RegisterType<Bus>("bus");
    carIOC.RegisterType<Track>("track");

    // 解析并创建 Bus 实例
    std::shared_ptr<ICar> bus = carIOC.ResolveShared("bus");
    bus->test();  // 调用 Bus 的 test 方法

    // 解析并创建 Track 实例
    std::shared_ptr<ICar> track = carIOC.ResolveShared("track");
    track->test();  // 调用 Track 的 test 方法

    system("pause");  // 暂停程序，以便查看输出结果
    return 0;  // 返回 0 表示程序正常结束
}